함수의 return은 오직 한개의 객체만 리턴한다. 보통 튜플로 리턴을 할 경우 여러개의 변수로 한번에 받게 할 수 있어 마치 return이 여러개의 값을 동시에 리턴하는 것처럼 보이지만 튜플이라는 객체 하나를 리턴하는 것이다.
In [5]:
def swap(a,b):
return b,a #튜플이 반환된다.
In [6]:
a = 1
b = 2
In [7]:
a,b = swap(a,b)
In [8]:
print(a,b)
In [9]:
print(swap)
함수가 생성되면 함수 자체도 객체이다. 그리고 그객체의 주소를 swap라는 변수가 참조한다.
In [10]:
def intersect(prelist, postlist):
ret_list = []
for x in prelist:
if x in postlist and x not in ret_list:
ret_list.append(x)
return ret_list
In [11]:
list1 = "HELLO"
list2 = "CLS"
In [12]:
print(intersect(list1, list2))
In [13]:
a = 10 # Namespace:global 이다.
b = 20 # Namespace:global 이다.
In [14]:
def sum(x,y):
return x+y
In [15]:
print(sum(a,b)) #x,y 가 글로벌 네임스테이스의 a,b의 주소를 참조하게 된다.
In [16]:
def sum2(x,y):
x = 1 # 1이라는 객체를 생성하고 그 주소를 변수 x가 새롭게 참조 한다. 변수 x의 네임스페이스는 sum2이다.
return x+y
In [17]:
x = 10 # 10은 이뮤터블이다. 즉 10 객체는 오퍼레이션이 없다. 10자체를 변경시키는 오퍼레이션이 없다.
In [18]:
print(sum2(x,b)) #x,y가 x=10 과 b를 참조한다. 그러나 sum2네임스페이스안에서 x는 새로운 객체 1을 참조 하는 것으로 변경 된다.
In [19]:
print(x)
In [36]:
def change(x):
print(x[0])
print(type(x[0]))
print(id(x))
print(id(x[0]))
print(id(x[1]))
print(id(x[2]))
x[0] = 'H'
In [37]:
w_list = ["S", "A", "M"] # 리스트는 뮤터블한 객체이다 함수 안에서 내용을 변경 할 수 있다. 뮤터블이기 때문에 그렇다.
In [38]:
change(w_list)
print(w_list)
In [39]:
def change2(x):
x = x[:] # clone를 해서 변경을 한다. 그러면 외부의 list는 그대로 있게 된다.
x[0] = "H"
In [41]:
w_list = ["S","A","M"]
print(w_list)
change2(w_list)
print(w_list)
nameSpace 는 프로그램에서 쓰이는 이름이 저장되는 공간이다. 여기서 이름이란 객체 참조 변수를 말하는 것이다. 함수 안에는 별도의 이름공간이 생성이 된다. 그 이름 공간을 Local scope, 함수 밖은 global scope 이라고 하고 파이썬에서 정의한 내용에 대한 영역을 내장 영역(built-in-scope)라고 한다. 함수 안에서 어떤 네임을 사용할 경우 그 함수 스코프 내에 이름이 없는경우 상의 스코프를 뒤진다. 찾는 순서는 Local -> global -> built-in 순으로 검색 한다. 이걸 스코핑 룰 이라 한다.
In [45]:
a = [1,2,3]
def scoping():
a = [4,5,6]
print(a)
In [46]:
scoping()
print(a)
In [61]:
x = 1
def func(a):
return a + x #x를 찾지만 local scope내의 이름공간에 x가 정의 되지 않았기 때문에 상위 scope에서 찾는다. 단 사용하는것 만가능함 상위 스코프의 변수에 조작은 못함
In [62]:
func(1)
Out[62]:
In [63]:
def func2(a):
x = 2
return a+x #x를 local scope내의 이름공간서 찾는데 있어서 그걸로 사용한다.
In [64]:
func2(1)
Out[64]:
In [71]:
def func3(a):
try:
x = x + 1
except UnboundLocalError:
print("에러 발생함")
else:
return a + x
In [72]:
func3(1)
global이 하는 일은 새로운 지역 변수를 만들거나 복사하는 것이 아니라 단지 전역 영역의 값을 지역 영역에 참조할 수 있게 전역변수의 레퍼런스를 지역변수 영역 이름공간에 생성하는 것이다.
In [73]:
g = 1
def testScope(a):
global g #전역 스코프에 존재하는 변수의 값을 변경 할 수 있게 한다.
g = 2 #java는 이렇게 하면 전역에 있는 값이 수정되지만 파이썬은 타입개념이 없어 이렇게만 하면 그냥 지역변수 선언이다 그래서 전역에 영향을 미치도록 하기 위해서 global을 사용한다.
return g + a
In [74]:
testScope(1)
Out[74]:
In [75]:
g
Out[75]:
In [76]:
print(dir())
In [79]:
print(dir(func2))
In [80]:
dir(__name__)
Out[80]:
In [83]:
print(globals())
In [84]:
def argTest(a,b,c):
print(a,b,c)
In [85]:
argTest(a=1,b=2,3) #키워드인자 들이 일반 인자보다 나중에 써야 한다.
In [86]:
argTest(1,a=1,b=2) #이렇게 하면 일반인자 뒤에 키워드 인자들을 사용했으니 될거 같은데 안된다.
In [87]:
argTest(1,b=2,c=3) #일반인자의 순서는 시그니처 순으로 무조건 와야 한다.
In [90]:
argTest(a=1,2,c=3) #이렇게 하더라도 두번째 인자인 2 앞에 키워드인자 a=1이 사용이되어서 안된다.
In [93]:
def test(*args):
print(type(args))
print(args)
In [94]:
test(1,2,3,4,5)
In [95]:
def union(*args):
res = []
for i in args:
for x in i:
if x not in res:
res.append(x)
return res
In [97]:
union("ham","mma", "spam")
Out[97]:
In [5]:
def urlBuilder(server, **args):
print(server)
for i in args.keys():
print(i, " : ",args[i])
In [8]:
urlBuilder("gg",a = "val_a", b = "val_b", c = "val_c")
In [12]:
(lambda x : x+1)(1)
Out[12]:
In [13]:
b = lambda x: x+1
In [14]:
b(3)
Out[14]:
아래와 같이 람다를 여러줄에 걸쳐 표현 할 수 있지만 안티 패턴이다.
In [20]:
def testLambda(g):
g(1,2,3)
In [21]:
testLambda(lambda a,b,c: print("sum id ", \
a+b+c, ": type id a ", type(a) ,\
":list object is ", zip([a,b,c])))
In [22]:
def fibo(n):
if n<2: return 1
return fibo(n-1) + fibo(n-2)
In [23]:
fibo(3)
Out[23]:
In [24]:
fibo(4)
Out[24]:
In [27]:
for i in range(0,10):
print(fibo(i))
In [39]:
temp = {}
In [40]:
def newFibo(n):
if n in temp.keys():
return temp[n]
if n<2:
temp[n] = 1
return 1
temp[n] = newFibo(n-1) + newFibo(n-2)
return temp[n]
In [41]:
newFibo(1)
Out[41]:
In [42]:
newFibo(2)
Out[42]:
In [43]:
newFibo(3)
Out[43]:
In [44]:
newFibo(4)
Out[44]:
In [55]:
temp = {}
for i in range(10):
print(newFibo(i))
In [56]:
print(temp)
In [2]:
def plus(a,b):
return a+b
In [3]:
help(plus)
In [5]:
def minus(a,b):
return a+b
In [6]:
help(minus)
In [7]:
plus.__doc__ = "a,b의 더한 값을 반환 합니다."
In [8]:
help(plus)
In [11]:
def fac(n):
"""
팩토리얼 함수 입니다.
>>> fac(6)
"""
if n == 1:
return n
return n * fac(n-1)
In [18]:
print(fac(3))
In [19]:
help(fac)
In [21]:
for key in {"a":1,"b":2}:
print(key)
시퀀스형 자료는 속성으로 이터레이터 객체를 가지고 있다.
In [22]:
s = "abc"
In [24]:
it = iter(s)
In [25]:
print(it)
In [27]:
next(it)
Out[27]:
In [28]:
next(it)
Out[28]:
In [29]:
next(it)
Out[29]:
In [30]:
next(it)
In [32]:
it.__next__()
In [33]:
it = iter(s)
In [34]:
it.__next__()
Out[34]:
In [35]:
it.__next__()
Out[35]:
In [36]:
it.__next__()
Out[36]:
In [37]:
it.__next__()
In [40]:
next(iter("ab"))
Out[40]:
In [ ]: